package com.sx.medicinecard.utils;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.*;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

public class DateUtils {

    /**
     * 获取一个时间几分钟后的时间（Date格式）
     * @param date
     * @param minute
     * @return
     */
    public static Date dateAfterMinute(Date date,int minute){
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        calendar.add(Calendar.MINUTE, minute); // 在当前时间上加5分钟
        return calendar.getTime();
    }


    /**
     * 获取一个时间几天后的时间（Date格式）
     * @param date
     * @param day
     * @return
     */
    public static Date dateAfterDay(Date date,int day){
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        calendar.add(Calendar.DAY_OF_WEEK, day);
        return calendar.getTime();
    }

    /**
     * 获取一个时间几分钟前的时间（LocalDate格式）
     * @param localDateTime
     * @param minute
     * @return
     */
    public static LocalDateTime localDateBeforeMinute(LocalDateTime localDateTime, int minute){
        return localDateTime.minusMinutes(minute);
    }

    /**
     * 将LocalDate转为Date
     * @param localDate
     * @return
     */
    public static Date localDateToDate(LocalDate localDate){
        Instant instant1 = localDate.atTime(LocalTime.MIDNIGHT).atZone(ZoneId.systemDefault()).toInstant();
        return Date.from(instant1);
    }

    /**
     * 将Date转为LocalDate
     * @param date
     * @return
     */
    public static LocalDate dateToLocalDate(Date date){
        Instant instant = date.toInstant();
        ZoneId zoneId = ZoneId.systemDefault();

        // atZone()方法返回在指定时区从此Instant生成的ZonedDateTime。
        LocalDate localDate = instant.atZone(zoneId).toLocalDate();
        System.out.println("Date = " + date);
        System.out.println("LocalDate = " + localDate);
        return localDate;
    }


    /**
     * 将Date日期按照format格式化
     * @param date
     * @param format
     * @return
     */
    public static String dateToStringWithFormat(Date date,String format){
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat(format);
        return simpleDateFormat.format(date);
    }

    /**
     * 将Date日期按照format格式化
     * @param localDate
     * @param format
     * @return
     */
    public static String localDateToStringWithFormat(LocalDate localDate,String format){
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern(format);
        return localDate.format(formatter);
    }

    /**
     * 根据当前日期返回中文的当前星期
     * @param date
     * @return
     */
    public static String getChineseWeekday(Date date) {
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        int weekday = calendar.get(Calendar.DAY_OF_WEEK);
        String[] chineseWeekdays = {"", "日", "一", "二", "三", "四", "五", "六"};
        return chineseWeekdays[weekday];
    }


    /**
     * 获取两个日期之间的日期列表
     * @param startDateStr
     * @param endDateStr
     * @return
     */
    public static List<String> generateDateRange(String startDateStr, String endDateStr) {
        // 解析输入的日期字符串
        LocalDate startDate = LocalDate.parse(startDateStr, DateTimeFormatter.ofPattern("yyyy-MM-dd"));
        LocalDate endDate = LocalDate.parse(endDateStr, DateTimeFormatter.ofPattern("yyyy-MM-dd"));

        // 创建一个列表来存储生成的日期字符串
        List<String> dateRange = new ArrayList<>();

        // 循环生成日期并添加到列表中
        LocalDate currentDate = startDate;
        while (!currentDate.isAfter(endDate)) {
            dateRange.add(currentDate.format(DateTimeFormatter.ofPattern("yyyy-MM-dd")));
            currentDate = currentDate.plusDays(1);
        }

        return dateRange;
    }

    /**
     * 判断字符串日期和date日期是否相等
     * @param stringDate
     * @param date
     * @return
     */
    public static Boolean stringEqualsDate(String stringDate, Date date) throws ParseException {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        Date date1 = sdf.parse(stringDate); // 将字符串解析为 Date 对象
        return date1.equals(date);
    }

    /**
     * String日期转为Date
     * @param stringDate
     * @param fmt
     * @return
     * @throws ParseException
     */
    public static Date stringToDate(String stringDate,String fmt) throws ParseException {
        SimpleDateFormat  formatter = new SimpleDateFormat(fmt);
        // 将字符串解析为 LocalDate 对象
        return formatter.parse(stringDate);
    }

    /**
     * Date日期转String
     * @param date
     * @param fmt
     * @return
     * @throws ParseException
     */
    public static String dateToString(Date date,String fmt){
        SimpleDateFormat  formatter = new SimpleDateFormat(fmt);
        // 将字符串解析为 LocalDate 对象
        return formatter.format(date);
    }

    /**
     * 获取当前日期
     * @return
     */
    public static String getCurrentDate() {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        return sdf.format(new Date());
    }

    /**
     * 从 java.util.Date 对象中获取月份
     *
     * @param date java.util.Date 对象
     * @return 月份的数值（1-12）
     */
    public static int getMonthFromDate(Date date) {
        // 将 Date 转换为 LocalDate
        LocalDate localDate = date.toInstant().atZone(ZoneId.systemDefault()).toLocalDate();
        // 获取月份
        return localDate.getMonthValue();
    }

    /**
     * 从 java.util.Date 对象中获取年份
     *
     * @param date java.util.Date 对象
     * @return 年份的数值
     */
    public static int getYearFromDate(Date date) {
        // 将 Date 转换为 LocalDate
        LocalDate localDate = date.toInstant().atZone(ZoneId.systemDefault()).toLocalDate();
        // 获取年份
        return localDate.getYear();
    }

    /**
     * 计算两个日期之间相差的月份数
     *
     * @param startDate 开始日期
     * @param endDate   结束日期
     * @return 相差的月份数
     */
    public static int getMonthsBetween(Date startDate, Date endDate) {
        Calendar startCalendar = Calendar.getInstance();
        startCalendar.setTime(startDate);
        Calendar endCalendar = Calendar.getInstance();
        endCalendar.setTime(endDate);

        int startYear = startCalendar.get(Calendar.YEAR);
        int startMonth = startCalendar.get(Calendar.MONTH);

        int endYear = endCalendar.get(Calendar.YEAR);
        int endMonth = endCalendar.get(Calendar.MONTH);

        return (endYear - startYear) * 12 + (endMonth - startMonth) + 1;
    }


    public static void main(String[] args) throws ParseException {
        Date startDate = stringToDate("2024-03-13 00:00:00","yyyy-MM-dd HH:mm:ss");
        Date endDate = stringToDate("2024-05-13 00:00:00","yyyy-MM-dd HH:mm:ss");

        System.out.println(getMonthsBetween(startDate, endDate));
    }
}
